package com.ys.chatserver.http.logic;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.eva.framework.Processor;
import com.eva.framework.dto.SysActionConst;
import com.eva.framework.utils.EndsExceptionFactory;
import com.google.gson.Gson;
import com.ys.chatserver.common.dto.cnst.RetResult;
import com.ys.chatserver.http.logic.dto.*;
import com.ys.chatserver.im.dto.ParamConfig;
import com.ys.chatserver.im.dto.ParamSupport;
import com.ys.chatserver.redis.RedisConfig;
import com.ys.chatserver.redis.RedisUtil;
import com.ys.chatserver.tool.EmptyUtils;

import java.util.ArrayList;
import java.util.List;
import java.util.Vector;

public class CaseDevProccessor implements SysActionConst, Processor {
    private Gson gson = new Gson();

    @Override
    public Object process(int job_dispatch_id, int action_id, Object newData, Object oldData, User user) throws Exception {
        Object ret = null;
        String newDataJSON = (String) newData;

        if (job_dispatch_id == JobDispatchConst.LOGIC_GROUP_CASE_DEV) {
            ret = maintainMgrCaseJobDispatcher(action_id, newDataJSON, oldData, user);
        } else {
            throw EndsExceptionFactory.INVALID_JOB_DISPATCHER_ID(job_dispatch_id);
        }
        return ret;
    }


    private Object maintainMgrCaseJobDispatcher(int actionId, String newDataJSON, Object oldData, User user) throws Exception {
        switch (actionId) {
            case ACTION_ADD_OBSERVER: {//添加观察员
                if (Boolean.TRUE.equals(isAdmin(user.getUserId()))) {
                    return gson.toJson(RetResult.failResult("权限拒绝,请使用普通账户"));
                }
                JSONObject jsonObject = JSON.parseObject(newDataJSON);
                String structureNo = jsonObject.getString("structureNo");
                String userUids = jsonObject.getString("userUids");
                if (EmptyUtils.isEmpty(structureNo) || EmptyUtils.isEmpty(userUids)) {
                    return gson.toJson(RetResult.failResult("参数错误!"));
                }
                if (Boolean.TRUE.equals(!exitStructure(structureNo, user.getUserId()))) {
                    return gson.toJson(RetResult.failResult("编号不存在或你不是创建者!"));
                }
                return addObserver(structureNo, userUids);
            }
            case ACTION_QUERY_OBSERVER: {//获取观察员列表
                JSONObject jsonObject = JSON.parseObject(newDataJSON);
                String structureNo = jsonObject.getString("structureNo");
                if (EmptyUtils.isEmpty(structureNo)) {
                    return gson.toJson(RetResult.failResult("参数错误!"));
                }
                if (Boolean.TRUE.equals(!exitStructure(structureNo, user.getUserId()))) {
                    return gson.toJson(RetResult.failResult("编号不存在或你不是创建者!"));
                }
                return queryObserverList(structureNo);
            }
            case ACTION_DELETE_OBSERVER: {//删除观察员
                if (Boolean.TRUE.equals(isAdmin(user.getUserId()))) {
                    return gson.toJson(RetResult.failResult("权限拒绝,请使用普通账户"));
                }
                JSONObject jsonObject = JSON.parseObject(newDataJSON);
                String structureNo = jsonObject.getString("structureNo");
                String userUids = jsonObject.getString("userUids");
                if (EmptyUtils.isEmpty(structureNo) || EmptyUtils.isEmpty(userUids)) {
                    return gson.toJson(RetResult.failResult("参数错误!"));
                }
                if (Boolean.TRUE.equals(!exitStructure(structureNo, user.getUserId()))) {
                    return gson.toJson(RetResult.failResult("案件不存在或你不是创建者!"));
                }
                return delObserver(structureNo, userUids);
            }
            case ACTION_ADD_DEVICE: {//添加设备
                if (Boolean.TRUE.equals(isAdmin(user.getUserId()))) {
                    return gson.toJson(RetResult.failResult("权限拒绝,请使用普通账户"));
                }
                JSONObject jsonObject = JSON.parseObject(newDataJSON);
                String structureNo = jsonObject.getString("structureNo");
                String devIds = jsonObject.getString("devIds");
                if (EmptyUtils.isEmpty(structureNo) || EmptyUtils.isEmpty(devIds)) {
                    return gson.toJson(RetResult.failResult("参数错误!"));
                }
                if (Boolean.FALSE.equals(isObserver(structureNo, user.getUserId()))) {
                    return gson.toJson(RetResult.failResult("暂无权限！"));
                }
                return addDevice(structureNo, devIds, user.getUserId());
            }
            case ACTION_QUERY_UNBINT_DEVICE: { //获取不在AJ下的设备列表
                List<QueryUserResVO> queryUserResVOS = queryUnUseDevice();
                return gson.toJson(RetResult.successResult("获取成功！", queryUserResVOS));
            }
            case ACTION_QUERY_DEVICE: {//获取AJ下的设备列表
                JSONObject jsonObject = JSON.parseObject(newDataJSON);
                String structureNo = jsonObject.getString("structureNo");
                return gson.toJson(RetResult.successResult("获取成功！", queryChildNode(structureNo)));
            }
            case ACTION_DELETE_DEVICE: {//删除案件下设备
                if (Boolean.TRUE.equals(isAdmin(user.getUserId()))) {
                    return gson.toJson(RetResult.failResult("权限拒绝,请使用普通账户"));
                }
                JSONObject jsonObject = JSON.parseObject(newDataJSON);
                String structureNo = jsonObject.getString("structureNo");
                String devIds = jsonObject.getString("devIds");
                if (EmptyUtils.isEmpty(structureNo) || EmptyUtils.isEmpty(devIds)) {
                    return gson.toJson(RetResult.failResult("参数错误!"));
                }
                if (Boolean.FALSE.equals(isObserver(structureNo, user.getUserId()))) {
                    return gson.toJson(RetResult.failResult("暂无权限！"));
                }
                return delDevice(structureNo, devIds);
            }
            default:
                throw EndsExceptionFactory.INVALID_ACTION_ID(actionId);
        }
    }


    /**
     * 判断是否为管理员用户
     *
     * @param userId
     * @return
     * @throws Exception
     */
    private Boolean isAdmin(String userId) throws Exception {
        String sql = "select account_type from g_users where del_flag = 0 and user_uid='" + userId + "'";
        Vector<Vector<?>> vector = LogicProcessor2.db.queryData(sql);
        Integer integer = Integer.valueOf((String) vector.get(0).get(0));
        return integer != 1;
    }


    /**
     * 判断组织是否存在
     *
     * @param structureNo
     * @return
     */
    private Boolean exitStructure(String structureNo, String creatorId) throws Exception {
        String sql = "select * from structure_info where structure_type=1 and structure_no='" + structureNo + "' and creator_id='" + creatorId + "'";
        Vector<Vector<?>> vector = LogicProcessor2.db.queryData(sql);
        return !vector.isEmpty();
    }

    /**
     * 设置观察员
     *
     * @param structureNo
     * @param userUids
     * @return
     * @throws Exception
     */
    public String addObserver(String structureNo, String userUids) throws Exception {
        List<String> userList = EmptyUtils.getListObjectSplitValue(userUids);
        List<String> list = new ArrayList<>();
        List<String> selectUser = new ArrayList<>();
        for (String userId : userList) {
            String sql = "select * from g_users where del_flag = 0 and user_uid='" + userId + "' and user_type=0";
            Vector<Vector<?>> vector0 = LogicProcessor2.db.queryData(sql);
            if (vector0.isEmpty()) {
                continue;
            }
            String sql1 = "select * from structure_user_info where user_id='" + userId + "' and structure_no='" + structureNo + "' and user_type='" + CaseUserType.OBSERVER.name() + "'";
            Vector<Vector<?>> vector1 = LogicProcessor2.db.queryData(sql1);
            if (!vector1.isEmpty()) {
                continue;
            }
            selectUser.add(userId);
            list.add("insert into structure_user_info(structure_no,user_id,user_type) values " +
                    "('" + structureNo + "','" + userId + "','" + CaseUserType.OBSERVER.name() + "');");
        }
        if (list.isEmpty()) {
            return gson.toJson(RetResult.failResult("用户[" + queryAccountById(userList) + "]已设置为此案件的观察员，请勿重复添加！"));
        }
        boolean update = LogicProcessor2.db.update(list, true);
        return update ? gson.toJson(RetResult.successResult("用户[" + queryAccountById(selectUser) + "]设置成功！")) : gson.toJson(RetResult.failResult("添加失败！"));
    }

    /**
     * 获取观察员列表
     */
    private Object queryObserverList(String structureNo) throws Exception {
        String sql = "select user_uid,user_mail,nickname,is_online,user_avatar_file_name," +
                "account_type from g_users WHERE del_flag = 0 and user_uid in (select user_id from " +
                "structure_user_info where structure_no='" + structureNo + "');";
        Vector<Vector<?>> vector = LogicProcessor2.db.queryData(sql);
        List<UserInfoVO> list = new ArrayList<>();
        for (Vector<?> v : vector) {
            int i = 0;
            UserInfoVO userInfoVO = new UserInfoVO();
            userInfoVO.setUserUid(v.get(i).toString());
            userInfoVO.setUserMail(v.get(++i).toString());
            userInfoVO.setNickname(v.get(++i).toString());
            userInfoVO.setIsOnline(Integer.valueOf(v.get(++i).toString()));
            userInfoVO.setUserAvatarFileName(v.get(++i).toString());
            userInfoVO.setAccountType(Integer.valueOf(v.get(++i).toString()));
            list.add(userInfoVO);
        }
        return gson.toJson(RetResult.successResult("查询成功！", list));
    }

    /**
     * 删除观察员
     *
     * @param structureNo
     * @param userUids
     * @return
     * @throws Exception
     */
    private Object delObserver(String structureNo, String userUids) throws Exception {
        List<String> userList = EmptyUtils.getListObjectSplitValue(userUids);
        List<String> list = new ArrayList<>();
        List<String> selectUser = new ArrayList<>();
        for (String userId : userList) {
            String sql = "select * from g_users where del_flag = 0 and user_uid='" + userId + "' and user_type=0";
            Vector<Vector<?>> vector0 = LogicProcessor2.db.queryData(sql);
            if (vector0.isEmpty()) {
                continue;
            }
            String sql1 = "select * from structure_user_info where user_id='" + userId + "' and structure_no='" + structureNo + "' and user_type='" + CaseUserType.OBSERVER.name() + "'";
            Vector<Vector<?>> vector1 = LogicProcessor2.db.queryData(sql1);
            if (vector1.isEmpty()) {
                continue;
            }
            selectUser.add(userId);
            list.add("delete from structure_user_info where structure_no='" + structureNo + "' and" +
                    " user_id='" + userId + "' and user_type='" + CaseUserType.OBSERVER.name() + "'");
        }

        boolean update = LogicProcessor2.db.update(list, true);
        return update ? gson.toJson(RetResult.successResult("观察员[" + queryAccountById(selectUser) + "]删除成功！")) : gson.toJson(RetResult.failResult("删除失败！"));
    }

    /**
     * 是否为AJ观察员
     */
    private Boolean isObserver(String structureNo, String userId) throws Exception {
        String sql = "select * from structure_user_info where structure_no=(select root_no from structure_info where structure_no='" + structureNo + "') and user_id='" + userId + "'";
        Vector<Vector<?>> vector = LogicProcessor2.db.queryData(sql);
        return !vector.isEmpty();
    }

    /**
     * 添加设备
     */
    private Object addDevice(String structureNo, String devIds, String userId) throws Exception {
        List<String> devList = EmptyUtils.getListObjectSplitValue(devIds);
        List<String> list = new ArrayList<>();
        List<String> selectDev = new ArrayList<>();
        for (String devId : devList) {
            String sql = "select * from g_users where del_flag = 0 and user_uid='" + devId + "' and user_type=1";
            Vector<Vector<?>> vector = LogicProcessor2.db.queryData(sql);
            if (vector.isEmpty()) {
                continue;
            }
            String sql1 = "select * from structure_user_info where user_id='" + devId + "'  and user_type='" + CaseUserType.DEVICE.name() + "' and is_finish=0";
            Vector<Vector<?>> vector1 = LogicProcessor2.db.queryData(sql1);
            if (!vector1.isEmpty()) {
                continue;
            }
            selectDev.add(devId);
            list.add("insert into structure_user_info(structure_no,user_id,user_type) values " +
                    "('" + structureNo + "','" + devId + "','" + CaseUserType.DEVICE.name() + "');");
            String sql2 = "select structure_no,is_finish from structure_user_info where user_id='" + userId + "' and user_type='" + CaseUserType.USER.name() + "'";
            Vector<Vector<?>> vector2 = LogicProcessor2.db.queryData(sql2);
            if (!vector2.isEmpty()) {
                list.add("insert into my_structure(dev_id,user_id,structure_no,is_finish) values " +
                        "('" + devId + "','" + userId + "','" + vector2.get(0).get(0) + "','" + vector2.get(0).get(1) + "');");
            }

        }
        if (list.isEmpty()) {
            String s = queryAccountById(devList);
            return gson.toJson(RetResult.failResult(EmptyUtils.isEmpty(s) ? "绑定失败" : "设备[" + s + "]已绑定案件，绑定失败！"));
        }

        boolean update = LogicProcessor2.db.update(list, true);
        return update ? gson.toJson(RetResult.successResult("设备[" + queryAccountById(selectDev) + "]绑定成功！")) : gson.toJson(RetResult.failResult("绑定失败！"));

    }


    private String queryAccountById(List<String> userIds) throws Exception {
        String sql = "select user_mail from g_users where del_flag = 0 and user_uid in ('" + EmptyUtils.getStringSplitValue(userIds) + "')";
        Vector<Vector<?>> vector = LogicProcessor2.db.queryData(sql);
        if (vector.isEmpty()) {
            return null;
        }
        List<String> list = new ArrayList<>();
        for (Vector<?> v : vector) {
            list.add(v.get(0).toString());
        }
        return EmptyUtils.getStringSplitValue(list);
    }

    /**
     * 获取未绑定或已结束设备列表
     */
    private List<QueryUserResVO> queryUnUseDevice() throws Exception {
        String sql = "select u.nickname,u.register_time,u.latest_login_time,u.dev_type,u.expire_time" +
                ",g.nickname creatorName,u.user_uid from g_users u " +
                " left join g_users g on g.user_uid = u.creator_id" +
                " where u.del_flag = 0" +
                " and u.user_type=1" +
                " and u.user_uid not in (select user_id FROM structure_user_info WHERE user_type='DEVICE' and is_finish=0)";
        Vector<Vector<?>> vector = LogicProcessor2.db.queryData(sql);
        List<QueryUserResVO> vos = new ArrayList<>();
        for (Vector<?> v : vector) {
            QueryUserResVO vo = new QueryUserResVO();
            int i = 0;
            String nickname = v.get(i).toString();
            String registerTime = v.get(++i).toString();
            String latestLoginTime = v.get(++i).toString();
            String type = v.get(++i).toString();
            String expireTime = v.get(++i).toString();
            String creatorName = v.get(++i).toString();
            String uid = v.get(++i).toString();
            vo.setUserUid(uid);
            vo.setNickname(nickname);
            vo.setRegisterTime(registerTime);
            vo.setDevType(Integer.valueOf(type));
            vo.setLatestLoginTime(latestLoginTime);
            vo.setExpireTime(expireTime);
            vo.setCreatorName(creatorName);
            vos.add(vo);
        }
        return vos;
    }


    /**
     * 获取下级节点及设备
     *
     * @param structureNo
     * @return
     * @throws Exception
     */
    private StructureUserVo queryChildNode(String structureNo) throws Exception {
        String querySql = "select structure_no,structure_name,structure_level," +
                "creator_id,creator_name,parent_no,is_finish,create_time,finish_time,structure_type,case_type from structure_info " +
                "where structure_type=1 and parent_no='" + structureNo + "' and parent_no!=structure_no";
        List<StructureInfoVO> structureInfoVOS = getStructureInfoVOS(querySql);
        StructureUserVo vo = new StructureUserVo();
        vo.setStructure(structureInfoVOS);
        vo.setUser(queryDevInfos(structureNo));
        return vo;
    }


    private List<StructureInfoVO> getStructureInfoVOS(String querySql) throws Exception {
        Vector<Vector<?>> vectors = LogicProcessor2.db.queryData(querySql);
        List<StructureInfoVO> vos = new ArrayList<>();
        if (vectors.isEmpty()) {
            return vos;
        }

        for (Vector<?> v : vectors) {
            int i = 0;
            StructureInfoVO vo = new StructureInfoVO();
            vo.setStructureNo(v.get(i).toString());
            vo.setStructureName(v.get(++i).toString());
            vo.setStructureLevel(v.get(++i).toString());
            vo.setCreatorId(v.get(++i).toString());
            vo.setCreatorName(v.get(++i).toString());
            vo.setParentNo(v.get(++i).toString());
            vo.setIsFinish(Integer.valueOf(v.get(++i).toString()));
            vo.setCreateTime(v.get(++i).toString());
            vo.setFinishTime(v.get(++i).toString());
            vo.setStructureType(Integer.valueOf(v.get(++i).toString()));
            vo.setCaseType(v.get(++i).toString());
            vos.add(vo);
        }
        return vos;
    }

    private StructureInfoVO obtainStructuresTree(List<StructureInfoVO> vos, StructureInfoVO vo) {
        List<StructureInfoVO> list = new ArrayList<>();
        for (StructureInfoVO v : vos) {
            if (v.getParentNo().equals(vo.getStructureNo())
                    && !v.getParentNo().equals(v.getStructureNo())) {
                list.add(v);
            }
        }
        if (!list.isEmpty()) {
            vo.setChildList(list);
            for (StructureInfoVO infoVO : vo.getChildList()) {
                obtainStructuresTree(vos, infoVO);
            }
        }
        return vo;
    }

    /**
     * 设备列表
     */
    private List<UserInfoVO> queryDevInfos(String structureNo) throws Exception {
        String sql = "SELECT user_uid,user_mail,nickname,is_online," +
                "user_avatar_file_name,account_type,user_type,dev_type FROM g_users WHERE del_flag = 0 and user_uid IN " +
                "(SELECT user_id FROM `structure_user_info`" +
                " WHERE structure_no = '" + structureNo + "' and user_type='DEVICE' and del_flag=0)";
        return getDevList(sql);
    }


    private List<UserInfoVO> getDevList(String sql) throws Exception {
        Vector<Vector<?>> vectors = LogicProcessor2.db.queryData(sql);
        List<UserInfoVO> vos = new ArrayList<>();
        if (!vectors.isEmpty()) {
            for (Vector<?> v : vectors) {
                int i = 0;
                UserInfoVO vo = new UserInfoVO();
                vo.setUserUid(v.get(i).toString());
                vo.setUserMail(v.get(++i).toString());
                vo.setNickname(v.get(++i).toString());
                vo.setIsOnline(Integer.valueOf(v.get(++i).toString()));
                vo.setUserAvatarFileName(v.get(++i).toString());
                vo.setAccountType(Integer.parseInt(v.get(++i).toString()));
                vo.setUserType(Integer.parseInt(v.get(++i).toString()));
                vo.setDevType(Integer.parseInt(v.get(++i).toString()));
                //redis 缓存中获取设备配置参数
                String support = RedisUtil.get(RedisConfig.getSupportKey(vo.getUserUid()));
                if (EmptyUtils.isNotEmpty(support)) {
                    ParamSupport paramSupport = JSON.parseObject(support, ParamSupport.class);
                    vo.setSupport(paramSupport);
                }
                String config = RedisUtil.get(RedisConfig.getConfigKey(vo.getUserUid()));
                if (EmptyUtils.isNotEmpty(config)) {
                    ParamConfig paramConfig = JSON.parseObject(config, ParamConfig.class);
                    vo.setConfig(paramConfig);
                }
                vos.add(vo);
            }
        }
        return vos;
    }


    /**
     * 删除案件下设备
     *
     * @param structureNo
     * @param userUids
     * @return
     * @throws Exception
     */
    private Object delDevice(String structureNo, String userUids) throws Exception {
        List<String> userList = EmptyUtils.getListObjectSplitValue(userUids);
        List<String> list = new ArrayList<>();
        List<String> selectUser = new ArrayList<>();

        for (String userId : userList) {
            String sql = "select * from g_users where del_flag = 0 and user_uid='" + userId + "' and user_type=1";
            Vector<Vector<?>> vector0 = LogicProcessor2.db.queryData(sql);
            if (vector0.isEmpty()) {
                continue;
            }
            String sql1 = "select * from structure_user_info where user_id='" + userId + "' and structure_no='" + structureNo + "' and user_type='" + CaseUserType.DEVICE.name() + "'";
            Vector<Vector<?>> vector1 = LogicProcessor2.db.queryData(sql1);
            if (vector1.isEmpty()) {
                continue;
            }
            selectUser.add(userId);
            list.add("update structure_user_info set del_flag=1 where structure_no='" + structureNo + "' and" +
                    " user_id='" + userId + "' and user_type='" + CaseUserType.DEVICE.name() + "'");
        }

        boolean update = LogicProcessor2.db.update(list, true);
        return update ? gson.toJson(RetResult.successResult("设备[" + queryAccountById(selectUser) + "]删除成功！")) : gson.toJson(RetResult.failResult("删除失败！"));
    }


}
